package cn.com.ry.framework.monitormeter.metric.http;

import cn.com.ry.framework.monitormeter.instrument.linklog.LinkLogMeterRegistry;
import io.micrometer.core.instrument.MeterRegistry;
import io.micrometer.core.instrument.Tags;
import io.micrometer.core.instrument.binder.MeterBinder;
import io.micrometer.prometheus.PrometheusMeterRegistry;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;

import java.util.function.ToDoubleFunction;

public class HttpClientPoolMetric implements MeterBinder {

    private String name;
    private PoolingHttpClientConnectionManager poolingHttpClientConnectionManager;

    public HttpClientPoolMetric(String name, PoolingHttpClientConnectionManager poolingHttpClientConnectionManager) {
        this.name = name;
        this.poolingHttpClientConnectionManager = poolingHttpClientConnectionManager;
    }

    @Override
    public void bindTo(MeterRegistry registry) {
        // 获取所有路由的连接池状态
        if (registry != null) {
            if (registry instanceof LinkLogMeterRegistry) {
                registry.gauge("httpclient." + name + ".max", poolingHttpClientConnectionManager, new ToDoubleFunction<PoolingHttpClientConnectionManager>() {
                    @Override
                    public double applyAsDouble(PoolingHttpClientConnectionManager value) {
                        return poolingHttpClientConnectionManager.getTotalStats().getMax();

                    }
                });
                registry.gauge("httpclient." + name + ".leased", poolingHttpClientConnectionManager, new ToDoubleFunction<PoolingHttpClientConnectionManager>() {
                    @Override
                    public double applyAsDouble(PoolingHttpClientConnectionManager value) {
                        return poolingHttpClientConnectionManager.getTotalStats().getLeased();

                    }
                });
                registry.gauge("httpclient." + name + ".pending", poolingHttpClientConnectionManager, new ToDoubleFunction<PoolingHttpClientConnectionManager>() {
                    @Override
                    public double applyAsDouble(PoolingHttpClientConnectionManager value) {
                        return poolingHttpClientConnectionManager.getTotalStats().getPending();

                    }
                });
                registry.gauge("httpclient." + name + ".available", poolingHttpClientConnectionManager, new ToDoubleFunction<PoolingHttpClientConnectionManager>() {
                    @Override
                    public double applyAsDouble(PoolingHttpClientConnectionManager value) {
                        return poolingHttpClientConnectionManager.getTotalStats().getAvailable();

                    }
                });
            } else if (registry instanceof PrometheusMeterRegistry) {
                registry.gauge("httpclient.pool.max", Tags.of("httpclient.pool.name", name), poolingHttpClientConnectionManager, new ToDoubleFunction<PoolingHttpClientConnectionManager>() {
                    @Override
                    public double applyAsDouble(PoolingHttpClientConnectionManager value) {
                        return poolingHttpClientConnectionManager.getTotalStats().getMax();

                    }
                });
                registry.gauge("httpclient.pool.leased", Tags.of("httpclient.pool.name", name), poolingHttpClientConnectionManager, new ToDoubleFunction<PoolingHttpClientConnectionManager>() {
                    @Override
                    public double applyAsDouble(PoolingHttpClientConnectionManager value) {
                        return poolingHttpClientConnectionManager.getTotalStats().getLeased();

                    }
                });
                registry.gauge("httpclient.pool.pending", Tags.of("httpclient.pool.name", name), poolingHttpClientConnectionManager, new ToDoubleFunction<PoolingHttpClientConnectionManager>() {
                    @Override
                    public double applyAsDouble(PoolingHttpClientConnectionManager value) {
                        return poolingHttpClientConnectionManager.getTotalStats().getPending();

                    }
                });
                registry.gauge("httpclient.pool.available", Tags.of("httpclient.pool.name", name), poolingHttpClientConnectionManager, new ToDoubleFunction<PoolingHttpClientConnectionManager>() {
                    @Override
                    public double applyAsDouble(PoolingHttpClientConnectionManager value) {
                        return poolingHttpClientConnectionManager.getTotalStats().getAvailable();

                    }
                });

            }
        }

    }
}
